package com.elf.reactnative;

import android.app.Activity;
import android.content.Intent;
import android.os.Bundle;
import android.support.annotation.NonNull;
import android.support.annotation.Nullable;
import android.support.v4.app.FragmentTransaction;
import android.support.v7.app.AppCompatActivity;
import android.text.TextUtils;
import android.view.KeyEvent;
import android.view.View;
import android.widget.Button;
import android.widget.LinearLayout;

import com.alibaba.fastjson.JSON;
import com.facebook.react.modules.core.DefaultHardwareBackBtnHandler;
import com.facebook.react.modules.core.PermissionAwareActivity;
import com.facebook.react.modules.core.PermissionListener;

import java.util.HashMap;
import java.util.Map;

public class ReactFragmentActivity extends AppCompatActivity
        implements DefaultHardwareBackBtnHandler, PermissionAwareActivity {

    private final static String ARG_BUNDLE_INFO = "bundleInfo";
    private final static String ARG_EXTRAS = "extras";

    private Map<Integer, ReactFragment> mFragmentMap = new HashMap<>();
    private ReactFragment mCurrentFragment;

    private LinearLayout layout_button;

    @Override
    protected void onCreate(@Nullable Bundle savedInstanceState) {
        super.onCreate(savedInstanceState);
        setContentView(R.layout.rn_activity_react_fragment);

        layout_button = findViewById(R.id.layout_button);

        ReactAppInfo reactAppInfo = getJsBundleInfo();
        if (reactAppInfo != null) {
            String[] names = reactAppInfo.mainComponentName.split(",");
            for (int i = 0; i < names.length; i++) {
                String name = names[i];
                ReactFragment fragment = new ReactFragment();
                fragment.createReactFragmentDelegate(this, reactAppInfo, name);
                mFragmentMap.put(i, fragment);

                Button button = new Button(this);
                button.setText(name);
                button.setTag(i);
                button.setOnClickListener(new View.OnClickListener() {
                    @Override
                    public void onClick(View v) {
                        showFragment((int) v.getTag());
                    }
                });
                layout_button.addView(button);
            }
        }

        mCurrentFragment = mFragmentMap.get(0);
    }

    protected ReactAppInfo getJsBundleInfo() {
        String jsBundleInfo = getIntent().getStringExtra(ARG_BUNDLE_INFO);
        return JSON.parseObject(jsBundleInfo, ReactAppInfo.class);
    }

    private synchronized void showFragment(int key) {

        FragmentTransaction fragmentTransaction = getSupportFragmentManager().beginTransaction();
        for (ReactFragment item : mFragmentMap.values()) {
            fragmentTransaction.hide(item);
        }

        mCurrentFragment = mFragmentMap.get(key);

        if (mCurrentFragment == null) {
            return;
        }

        if (mCurrentFragment.isLoaded()) {
            fragmentTransaction.show(mCurrentFragment);
        } else {
            fragmentTransaction.add(R.id.fragment_react, mCurrentFragment);
            fragmentTransaction.show(mCurrentFragment);
            mCurrentFragment.loaded();
        }

        fragmentTransaction.commit();
    }


    @Override
    public void invokeDefaultOnBackPressed() {
        super.onBackPressed();
    }

    @Override
    public void requestPermissions(String[] permissions, int requestCode, PermissionListener listener) {
        mCurrentFragment.getReactFragmentDelegate().requestPermissions(permissions, requestCode, listener);
    }

    @Override
    public void onRequestPermissionsResult(int requestCode, @NonNull String[] permissions, @NonNull int[] grantResults) {
        super.onRequestPermissionsResult(requestCode, permissions, grantResults);
        mCurrentFragment.getReactFragmentDelegate().onRequestPermissionsResult(requestCode, permissions, grantResults);
    }

    //----- 生命周期 通过ReactActivityDelegateImpl 传递

    @Override
    public void onNewIntent(Intent intent) {
        for (ReactFragment item : mFragmentMap.values()) {
            if (item.getReactFragmentDelegate() == null || !item.getReactFragmentDelegate().onNewIntent(intent)) {
                super.onNewIntent(intent);
            }
        }
    }

    @Override
    protected void onPause() {
        super.onPause();
        for (ReactFragment item : mFragmentMap.values()) {
            if (item.getReactFragmentDelegate() != null) {
                item.getReactFragmentDelegate().onPause();
            }
        }
    }

    @Override
    protected void onResume() {
        super.onResume();
        for (ReactFragment item : mFragmentMap.values()) {
            if (item.getReactFragmentDelegate() != null) {
                item.getReactFragmentDelegate().onResume();
            }
        }
    }

    @Override
    protected void onDestroy() {
        super.onDestroy();
        for (ReactFragment item : mFragmentMap.values()) {
            if (item.getReactFragmentDelegate() != null) {
                item.getReactFragmentDelegate().onDestroy();
            }
        }
    }

    @Override
    public void onActivityResult(int requestCode, int resultCode, Intent data) {
        for (ReactFragment item : mFragmentMap.values()) {
            if (item.getReactFragmentDelegate() != null) {
                item.getReactFragmentDelegate().onActivityResult(requestCode, resultCode, data);
            }
        }
    }

    @Override
    public boolean onKeyDown(int keyCode, KeyEvent event) {
        try {
            return mCurrentFragment.getReactFragmentDelegate().onKeyDown(keyCode, event) || super.onKeyDown(keyCode, event);
        } catch (AssertionError e) {
            e.printStackTrace();
        } catch (Exception e) {
            e.printStackTrace();
        }
        return super.onKeyDown(keyCode, event);
    }

    @Override
    public boolean onKeyUp(int keyCode, KeyEvent event) {
        try {
            return mCurrentFragment.getReactFragmentDelegate().onKeyUp(keyCode, event) || super.onKeyUp(keyCode, event);
        } catch (AssertionError e) {
            e.printStackTrace();
        } catch (Exception e) {
            e.printStackTrace();
        }
        return super.onKeyUp(keyCode, event);
    }

    @Override
    public boolean onKeyLongPress(int keyCode, KeyEvent event) {
        try {
            return mCurrentFragment.getReactFragmentDelegate().onKeyLongPress(keyCode, event) || super.onKeyLongPress(keyCode, event);
        } catch (AssertionError e) {
            e.printStackTrace();
        } catch (Exception e) {
            e.printStackTrace();
        }
        return super.onKeyLongPress(keyCode, event);
    }

    @Override
    public void onBackPressed() {
        if (!mCurrentFragment.getReactFragmentDelegate().onBackPressed()) {
            super.onBackPressed();
        }
    }

    //----- 生命周期 通过ReactActivityDelegateImpl 传递  end

    public static void open(Activity activity, String jsBundleInfo, String extras, int requestCode) {
        Intent intent = new Intent(activity, ReactFragmentActivity.class);
        intent.putExtra(ARG_BUNDLE_INFO, jsBundleInfo);
        if (!TextUtils.isEmpty(extras)) {
            intent.putExtra(ARG_EXTRAS, extras);
        }
        activity.startActivityForResult(intent, requestCode);
    }
}
